/**
 * zj 2024 04 12
 */
export class addContextMenu {
  constructor(option) {
    this.option = option;
    this.init();
  }

  async init() {
    let event = null;
    let menuDom = await this.addmenuDomBody();
    // console.warn("menuDommenuDom", menuDom);

    //
    for (let index = 0; index < this.option.data.length; index++) {
      let element = this.option.data[index];
      //判断是文字还是线条
      let str;
      if (element?.text) {
        //添加文字
        str = `<li class='content-menu-item ${element.className} item${index}'><span>${element.text}</span></li>`;
      } else {
        //添加线条
        str = `<li class='${element.className} item${index}'></li>`;
      }
      //添加到容器
      let liDom = this.htmlStr2HtmlDom(str);
      let menuListDom = menuDom.querySelector(".content-menu-list");
      menuListDom.appendChild(liDom);
      //需要在添加到页面上后，才能操作dom，因为liDom无法直接添加属性和事件，所以选择querySelector
      //console.warn("item", document.querySelector(`.item${index}`));
      document
        .querySelector(`.item${index}`)
        .addEventListener("click", function () {
          element?.action && element["action"](event);
        });
    }

    //
    // console.warn("menuDom.offsetHeight", menuDom.offsetHeight);
    // console.warn("getComputedStyle(menuDom)", getComputedStyle(menuDom));
    let menuHeight =
      menuDom.offsetHeight -
      parseInt(getComputedStyle(menuDom)["paddingTop"]) -
      parseInt(getComputedStyle(menuDom)["paddingBottom"]);
    let menuWidth =
      menuDom.offsetWidth -
      parseInt(getComputedStyle(menuDom)["paddingLeft"]) -
      parseInt(getComputedStyle(menuDom)["paddingRight"]);
    // console.warn("menuWidth", menuWidth);
    // console.warn("menuHeight", menuHeight);
    menuDom.style.height = "0";

    //dom绑定鼠标右键事件
    for (let index = 0; index < this.option.bindSelector.length; index++) {
      let selector = this.option.bindSelector[index];
      let selectorDom = document.querySelector(selector);
      selectorDom.oncontextmenu = (e) => {
        // console.warn("e", e);
        event = e;
        e.preventDefault();

        //禁止出底部和右侧
        let top = null;
        let left = null;
        if (window.innerHeight - e.clientY < menuHeight) {
          top = e.clientY - menuHeight;
        } else {
          top = e.clientY;
        }
        if (window.innerWidth - e.clientX < menuWidth) {
          left = e.clientX - menuWidth;
        } else {
          left = e.clientX;
        }

        //先清除在添加
        menuDom.style.height = "0";
        menuDom.classList.remove("is-active");
        setTimeout(() => {
          menuDom.style.left = `${left}px`;
          menuDom.style.top = `${top}px`;
          menuDom.style.height = `${menuHeight}px`;
          menuDom.classList.add("is-active");
        }, 300);
        return false;
      };
    }

    // 设置可以关闭弹窗的dom
    let closeSelector = this.option.closeSelector;
    if (this.option.closeSelector) {
      document.querySelector(closeSelector).onclick = () => {
        menuDom.style.height = "0";
        menuDom.classList.remove("is-active");
      };
    }
  }

  async addmenuDomBody() {
    return new Promise((reslove, reject) => {
      //每次先清空在添加
      let contentMenu = document.querySelector(".content-menu");
      if (contentMenu) {
        document.body.removeChild(contentMenu);
      }
      //
      let domString = `<div class="content-menu"><ul class="content-menu-list"></ul></div>`;
      let template = document.createElement("template");
      template.innerHTML = domString;
      let fragment = template.content;
      //
      let fn = () => {
        //console.warn("document.body", document.body);
        if (document.body) {
          document.body.appendChild(fragment);
          //console.warn("fragment", fragment);
          //fragment无法直接添加id
          let menuDom = document.querySelector(".content-menu");
          menuDom.id = this.option.addId;
          menuDom.classList.add(this.option.addClass);
          //console.warn("menu", menu);
          return reslove(menuDom);
        } else {
          return setTimeout(() => {
            return fn();
          }, 0);
        }
      };
      fn();
    });
  }

  htmlStr2HtmlDom(htmlStr) {
    let template = document.createElement("template");
    template.innerHTML = htmlStr;
    let fragment = template.content;
    return fragment;
  }
}
